// ==UserScript==
// @name        Ci Helper
// @namespace   Violentmonkey Scripts
// @match       https://gitee.com/openharmony/*/pulls/*
// @version     1.0.13
// @author      milkpotatoes
// @require     ../utils/utils.js
// @require     ./ci-helper-buttons.js
// @homepageURL https://gitee.com/milkpotatoes/tools-for-openharmony-repo
// @description Shortcuts for trigger Openharmony ci GGWatch and some others
//
// Promissions
// premissions to request user script API
// @grant       GM.getResourceUrl
// @grant       GM.getResourceText
//
// Resources
// stylesheet for ci helper
// @resource    CI_HELPER_STYLE           ci-helper-style.css
// stylesheets under here
// @resource    MD_ICON_ALL_CSS           https://unpkg.com/material-icons@1.13.12/iconfont/material-icons.css
// @resource    MD_ICON_FILLED_CSS        https://unpkg.com/material-icons@1.13.12/iconfont/filled.css
// @resource    MD_ICON_OUTLINED_CSS      https://unpkg.com/material-icons@1.13.12/iconfont/outlined.css
// @resource    MD_ICON_ROUND_CSS         https://unpkg.com/material-icons@1.13.12/iconfont/round.css
// @resource    MD_ICON_SHARP_CSS         https://unpkg.com/material-icons@1.13.12/iconfont/sharp.css
// @resource    MD_ICON_TWO_TONE_CSS      https://unpkg.com/material-icons@1.13.12/iconfont/two-tone.css
// woff fonts under here
// @resource    MD_ICON_FILLED_WOFF       https://unpkg.com/material-icons@1.13.12/iconfont/material-icons.woff
// @resource    MD_ICON_OUTLINED_WOFF     https://unpkg.com/material-icons@1.13.12/iconfont/material-icons-outlined.woff
// @resource    MD_ICON_ROUND_WOFF        https://unpkg.com/material-icons@1.13.12/iconfont/material-icons-round.woff
// @resource    MD_ICON_SHARP_WOFF        https://unpkg.com/material-icons@1.13.12/iconfont/material-icons-sharp.woff
// @resource    MD_ICON_TWO_TONE_WOFF     https://unpkg.com/material-icons@1.13.12/iconfont/material-icons-two-tone.woff
// woff2 fonts under here
// @resource    MD_ICON_FILLED_WOFF2      https://unpkg.com/material-icons@1.13.12/iconfont/material-icons.woff2
// @resource    MD_ICON_OUTLINED_WOFF2    https://unpkg.com/material-icons@1.13.12/iconfont/material-icons-outlined.woff2
// @resource    MD_ICON_ROUND_WOFF2       https://unpkg.com/material-icons@1.13.12/iconfont/material-icons-round.woff2
// @resource    MD_ICON_SHARP_WOFF2       https://unpkg.com/material-icons@1.13.12/iconfont/material-icons-sharp.woff2
// @resource    MD_ICON_TWO_TONE_WOFF2    https://unpkg.com/material-icons@1.13.12/iconfont/material-icons-two-tone.woff2
// ==/UserScript==


'use strict';

class GiteeUtils extends PrUtils {
    static isLogin() {
        return document.querySelector('.git-nav-user__login-item') === null;
    }

    static getPRAuthor() {
        return document.querySelector('.pull-request__subject .author_link').getAttribute('data-username');
    }

    static getLoginUser() {
        return document.querySelector('.form-with-gravatar').getAttribute('data-username');
    }

    static getWebLang() {
        const webLang = RegExp(/user_locale=([\w-]+?)(;|$)/).exec(document.cookie);
        return webLang ? webLang[1] : navigator.language;
    }

    static getPRState() {
        const stateCard = document.querySelector('.merge-state.pull-request');
        const stateClassList = stateCard.classList;
        if (stateClassList.contains('closed')) {
            return Utils.PR_STATE.CLOSED;
        }

        if (stateClassList.contains('merged')) {
            return Utils.PR_STATE.MERGED;
        }

        return Utils.PR_STATE.OPEN;
    }

    static getPRPage() {
        const page = location.pathname.split('/').pop();
        const prId = RegExp(/\d+/).exec(page);
        switch (page) {
            case 'diffs':
                return Utils.PR_PAGE.FILES;
            case 'check':
                return Utils.PR_PAGE.CHECKS;
            case 'commit':
                return Utils.PR_PAGE.COMMITS;
            default:
                if (prId && prId[0].length === page.length) {
                    return Utils.PR_PAGE.COMMENTS;
                } else {
                    return Utils.PR_PAGE.UNKNOWN;
                }
        }
    }

    static bind() {
        Utils.bindPrUtils(GiteeUtils);
    }
}
GiteeUtils.bind();

class GiteeHelperUtils extends HelperUtils {
    getCommentEditor() {
        const commentContainer = document.querySelector('.comments-wrapper.comments-no-blank~div');
        if (!commentContainer) {
            return;
        }

        const commentEditor = commentContainer.querySelector('textarea');
        return commentEditor;
    }

    /**
     * 
     * @param {Event} e 
     * @param {string?} message 
     */
    triggerButtonComment(e, message) {
        const editor = this.getCommentEditor();
        if (!editor) {
            return;
        }

        editor.focus();
        const commentBtns = document.querySelectorAll('.note-actions>.comment__action-group');
        const commentBtn = commentBtns.item(commentBtns.length - 1);

        const target = e.handleTarget ?? e.target;
        const msg = message ?? target.getAttribute('data');
        editor.value = msg;
        const event = new Event('input');

        editor.dispatchEvent(event);
        commentBtn.querySelector('.js-comment-button').click();
    }

    switchToComment(_) {
        document.querySelector('#pull-request-tabs [data-tab=pull-request-details]').click();
    }
    goToComment(_) {
        const commentContainer = document.querySelector('.comments-wrapper.comments-no-blank~div');
        if (!commentContainer) {
            return;
        }

        const commentEditor = commentContainer.querySelector('textarea');

        const rect = commentContainer.getBoundingClientRect();
        const distance = rect.top + rect.height - document.body.offsetHeight + 64;

        if (distance <= 64 && distance >= -256) {
            commentEditor.focus();
            return;
        }
        document.documentElement.scrollBy({
            left: 0,
            top: distance,
            behavior: "smooth",
        });

        const cancelTimer = () => { clearTimeout(timer); }
        const timer = setTimeout((editor) => {
            document.removeEventListener('wheel', cancelTimer);
            editor.focus();
        }, Math.max(500, distance / 10), commentEditor);
        document.addEventListener('wheel', cancelTimer, { once: true });
    }
    openLoginDialog(_) {
        document.querySelector('.git-nav-user__login-item').click();
    }
}
InitHelperUtils(new GiteeHelperUtils());

const initTools = (shadowRoot) => {
    helpBtns.forEach((btnInfo) => {
        if (!Utils.getButtonEnabled(btnInfo)) {
            return;
        }
        const btn = genHelperButton(btnInfo);
        shadowRoot.append(btn);
    });
}

const deinitTools = (shadowRoot) => {
    shadowRoot.querySelectorAll('button').forEach(e => {
        e.remove();
    });
}

const main = () => {
    const prCard = document.querySelector('.pull-request__merge-widget');
    if (prCard === null) {
        return;
    }

    const toolbar = document.createElement('div');
    toolbar.classList.add('ci-helper-toolbar');
    document.body.append(toolbar);
    document.querySelector('.bottombar').style.paddingBottom = '72px';

    const shadowRoot = toolbar.attachShadow({ mode: 'closed' });

    MaterialIcon.getMDIconCss(MaterialIcon.ICON_TYPE.FILLED)
        .then((styles) => {
            styles.apply(shadowRoot);
        });

    const styleSheet = new CSSStyleSheet();
    const css = GM.getResourceText('CI_HELPER_STYLE');
    if (typeof css === 'string') {
        styleSheet.replace(css)
            .then(e => {
                shadowRoot.adoptedStyleSheets.push(e);
            });
    } else {
        css.then(style => {
            styleSheet.replace(style)
                .then(e => {
                    shadowRoot.adoptedStyleSheets.push(e);
                });
        })
    }

    initTools(shadowRoot);

    document.querySelector('#pull-request-tabs').addEventListener('click', () => {
        setTimeout(() => {
            deinitTools(shadowRoot);
            initTools(shadowRoot);
        }, 50);
    });

    toolbar.animate([
        { transform: 'translate(calc(-50% - 1em), 100%)' },
        { transform: 'translate(calc(-50% - 1em), 0)' },
    ], {
        easing: 'ease-in',
        duration: 500,
    });
    return toolbar;
};

setTimeout(main, 1000);